home *** CD-ROM | disk | FTP | other *** search
/ Amiga Plus 2004 #11 / Amiga Plus CD - 2004 - No. 11.iso / AmiSoft / Dev / misc / temgen.lha / Temgen / tg-0.11 / atom.c < prev    next >
C/C++ Source or Header  |  2002-12-18  |  2KB  |  81 lines

  1. #include "sysdefs.h"
  2.  
  3. #include "alloc.h"
  4. #include "crc.h"
  5. #include "list.h"
  6. #include "atom.h"
  7.  
  8. #define   HSIZE     419
  9.  
  10. struct atomstr {
  11.     struct list_head name_list;
  12.     struct list_head id_list;
  13.     int id;
  14.     char *name;
  15. };
  16.  
  17. static int first_free = 0;
  18. static struct list_head name_hash[ HSIZE ];
  19. static struct list_head id_hash[ HSIZE ];
  20.     
  21. static void init_atoms()
  22. {
  23.     int i;
  24.     
  25.     first_free = 1;
  26.     
  27.     for ( i=0; i<HSIZE; i++ ) {
  28.         INIT_LIST_HEAD( name_hash + i );
  29.         INIT_LIST_HEAD( id_hash + i );
  30.     }
  31. }
  32.  
  33. int atom( const char *name )
  34. {
  35.     unsigned hv;
  36.     struct list_head *it;
  37.     struct atomstr *a;
  38.     
  39.     if ( !first_free ) init_atoms();
  40.     hv = crc32_0( name ) % HSIZE;
  41.     
  42.     for ( it = name_hash[ hv ].next; it != name_hash+hv; it = it->next ) {
  43.         a = list_entry( it, struct atomstr, name_list );
  44.         if ( !strcmp( a->name, name ) ) return a->id;
  45.     }
  46.     
  47.     a = (struct atomstr*)MALLOC( sizeof(*a) );
  48.     if ( !a ) return 0;
  49.     
  50.     a->id = first_free++;
  51.     a->name = STRDUP( name );
  52.     if ( !a->name ) {
  53.         FREE( a );
  54.         first_free--;
  55.         return 0;
  56.     }
  57.     
  58.     list_add( &( a->name_list ), name_hash + hv );
  59.     list_add( &( a->id_list ), id_hash + (a->id % HSIZE) );
  60.     return a->id;
  61. }
  62.  
  63. const char *atom_name( int id )
  64. {
  65.     unsigned hv;
  66.     struct list_head *it;
  67.     struct atomstr *a;
  68.     
  69.     if ( id <= 0 ) return NULL;
  70.     
  71.     if ( !first_free ) init_atoms();
  72.     hv = id % HSIZE;
  73.     
  74.     for ( it = id_hash[ hv ].next; it != id_hash+hv; it = it->next ) {
  75.         a = list_entry( it, struct atomstr, id_list );
  76.         if ( a->id == id ) return a->name;
  77.     }
  78.     
  79.     return NULL;
  80. }
  81.